<?php        
#using ('Origami_XML_Reader');
#using ('Origami_XSL_Transformer');

define ("DOWNLOAD_PACKET_VOLUME", 25000);   
using ('News_Usenet_Article');
using ('News_UI_ControlFactory');
using ('News_UI_View');

function sel($x){return $x?' selected="selected" ':'';}
function hte($x){return str_replace('&amp;', '&', htmlentities($x)); }
class News_UI_Articlelist
{
    var $Controller;
    var $List;
    var $groupName;
    var $groupData;
    function News_UI_Articlelist($controller, $load = true)
    {
        $this->Controller = $controller;
        $this->groupName  = $this->Controller->Settings['group']; 
        $this->groupData  = array();
        
        if ($this->Controller->Settings['subscribe'] == 'ok')
        {
            $this->Subscribe ();
            $pageindex  = $this->Controller->Settings['page']; 
            $find       = $this->Controller->Settings['find']; 
            $uri        = $this->Controller->URI (array('subscribe' => NULL));//"/ui/articlelist/group/{$this->groupName}/page/{$pageindex}";
            redirect ($uri); 
        }
    }
    
    function Subscribe()
    {         
        $subdata = $this->Controller->Read ('data/subdata.txt');
        parse_str($subdata);
        $me  = array();
        $ok  = true;
        $out = array();
        if (isset($my))
        {
            for ($x=0;$x<sizeof($my);$x++)
            {
                if ($my[$x]==$this->groupName)
                {
                    $ok = false;
                }
                else
                {
                    $me[] = $my[$x];
                }
            }
        }
        if ($ok)
        {
            $me[] = $this->groupName;
        }
        for ($x=0;$x<sizeof($me);$x++)
        {
            $out[] = "my[]=" . $me[$x];
        }
        $this->Controller->Save ('data/subdata.txt', implode ('&', $out));
    }
    
    function Subscribed()
    {         
        $subdata = $this->Controller->Read ('data/subdata.txt');
        parse_str($subdata);
        if (isset($my))
        {
            for ($x=0;$x<sizeof($my);$x++)
            {
                if ($my[$x]==$this->groupName)
                {
                    return true;
                }
            }
        }
        return false; 
    }
	
	function Download ($param = NULL)
	{ 
        $nntp = $this->Controller->Server->NNTP;
		$fp   = fopen ('data/' . $this->groupName . '.dat', 'a');
		
        if (!$nntp->connect())                                                
        {                                                
            header("Content-Error: " . $nntp->get_error_message());                                               
            echo "<b>".$messages_ini["error"]["nntp_fail"]."</b><br>";                                                
            echo $nntp->get_error_message().$nntp_server."<br>";                                                
            return;                                               
        }  
         
        if ( $gi=$nntp->join_group(trim($this->groupName)) )                                               
        {
        	if ($param) $param = strtolower($param);                                     
            $minimum    = $gi['start_id'];                               
            $maximum    = $gi['end_id'];                                 
            $start_id   = min ($minimum, $maximum);                        
            $max_id     = max ($minimum, $maximum);  
          
		    
            $nntp_query = "XOVER " . $start_id . "-" . $max_id;    
            $buf        = $nntp->send_request( $nntp_query );                                                   
            $response   = $nntp->parse_response($buf);   
            if ($response["status"] == ARTICLE_OVERVIEW || $response["status"] == ARTICLE_HEAD)                                                
            {                                         
                $buf = fgets($nntp->nntp, 4096);    
                while (!preg_match("/^\.\s*$/", $buf))                                                
                {
                	if ($param == NULL || strpos($buf, $param))
					{
                	    fputs($fp, $buf);    
					}
                    $buf = fgets($nntp->nntp, 4096);     
                }              
            }
        }                        
        $nntp->quit();     
		fclose ($fp);
		
		
		
		
	} 

	function ViewasHiLo ($xml, $data)
	{ 
        $upindex   = $this->Controller->Settings['up'];
        $dnindex   = $this->Controller->Settings['dn']; 
        $paneindex = $this->Controller->Settings['pane'];
        $index     = $this->Controller->Settings['index'];
        $result    = $xml->xpath("//list/article[@index='{$index}']/items/article");
        if (strlen($upindex) == 0) $upindex = sizeof($result);
	    if (strlen($dnindex) == 0) $dnindex = 0;
		 
		$dotrix = $this->Controller->CreateHiLo (0, sizeof($result), 50);
        $matrix = $this->Controller->CreateHiLo ($dnindex, $upindex);
        $result = $this->Controller->SortArticles ($result);
	 

        $dots = array();
        $uri  = $this->Controller->URI (array('ui'      => 'commandhandler',
                                              'request' => 'hilo', 
                                              'dn'      => NULL
                                        ));
		$dots[] = "<input size='3' onchange='location.href=this.className+this.value' class='{$uri}/dn/' value='{$dnindex}'/>";
        for ($i=0;$i<sizeof($dotrix);$i++)
		{
			$n = $dotrix[$i];
			if ($n < $dnindex || $n > $upindex)
			{
			    $way     = $n < $dnindex ? 'dn' : 'up';
                $up      = $this->Controller->URI (array('ui'      => 'commandhandler',
                                                         'request' => 'hilo',
                                                         $way      => $n));
													 
			    $dots[] = sprintf('<a href="%s">%s</a>', $up, '&bull;');
			}
			else {
				$dots[] = '<font color=lime>&bull;</font>';
			}
		}
        $uri  = $this->Controller->URI (array('ui'      => 'commandhandler',
                                              'request' => 'hilo', 
                                              'up'      => NULL
                                        ));
		$dots[] = "<input size='3' onchange='location.href=this.className+this.value' class='{$uri}/up/' value='{$upindex}'/>";
        $data['controlbar'] = implode (' ', $dots);
		
        
        $value     = $result[0]->subject; 
        $fave      = $this->Controller->URI (array('ui'      => 'commandhandler',
                                                    'request' => 'mark'));
         
        $back      = $this->Controller->URI (array('index'   => NULL,
                                                   'pane'    => NULL, 'up'=>NULL, 'dn'=>NULL, 'view'=>NULL ));
        $fave    = $this->Controller->URI (array('ui'      => 'commandhandler',
                                                 'request' => 'mark')); 
        $bfave   = $this->Controller->Factory->Button ($fave, 'Bookmark', 'i.p.cont.individual.gif'); 
        
        $data['header']  = "<a href='/ui/'>Home</a> &#187; ";
        $data['header'] .= sprintf("<a href='%s'>%s</a> &#187; %s", $back, $this->groupName, $value); 
        $data['header'] .= "<div style='float:right'>{$bfave}</div>";
		
		
        for ($i=0;$i<sizeof($matrix);$i++)
        {
                $x       = $matrix[$i];
                $name    = $result[$x]->id; 
                $value   = $result[$x]->subject; 
                $b64     = base64_encode ($name);
                $up      = $this->Controller->URI (array('ui'      => 'commandhandler',
                                                         'request' => 'hilo',
                                                         'up'      => $x));
                $dn      = $this->Controller->URI (array('ui'      => 'commandhandler',
                                                         'request' => 'hilo',
                                                         'dn'      => $x));
													 
                $bdn     = $this->Controller->Factory->Button ($dn, 'Down', 'i.p.previous.gif'); 
                $bup     = $this->Controller->Factory->Button ($up, 'Up', 'i.p.next.gif'); 
													 
                $uri     = $this->Controller->URI (array('item'    => $name,
                                                         'pane'    => NULL, 'up'=>NULL, 'dn'=>NULL, 'view'=>NULL ));
                $src     = "/ui/image/group/{$this->groupName}/id/{$name}/thumb/ok";
                $data['main'] .= $this->Controller->Factory->Thumbnail ($src, $uri, $x . '. ' . $value . "<br>{$bdn}{$bup}");
        }
        return $this->Controller->Structure ($data); 
    }
    
	
	function ViewasBrowse ($xml, $data)
	{ 
        $paneindex = $this->Controller->Settings['pane'];
        $index     = $this->Controller->Settings['index'];
        $result    = $xml->xpath("//list/article[@index='{$index}']/items/article");
        $hi        = $paneindex * UI_PAGE_SIZE;
        $low       = $hi - UI_PAGE_SIZE;
        $value     = $result[0]->subject; 
        $fave      = $this->Controller->URI (array('ui'      => 'commandhandler',
                                                   'request' => 'mark'));
         
        $ask       = array( 'ui'      => 'commandhandler', 
	                        'request' => 'browse', 
	                        'pane'    => NULL,  
	                        'group'   => $this->groupName,  
	                        'index'   => $index
	                        );  
        $hilo      = array( 'ui'      => 'commandhandler', 
	                        'request' => 'hilo', 
	                        'dn'      => '0', 
	                        'up'      => sizeof ($result), 
	                        'pane'    => $paneindex,  
	                        'group'   => $this->groupName,  
	                        'index'   => $index
	                        );  
        $back      = $this->Controller->URI (array('index'   => NULL,
                                                   'pane'    => NULL));
        
        $bfave     = $this->Controller->Factory->Button ($fave, 'Bookmark', 'i.p.cont.individual.gif'); 
        $bhilo     = $this->Controller->Factory->Button ($this->Controller->URI($hilo), 'Hi-Low', 'i.p.search.gif'); 
                                    
        $data['controlbar'] = $this->Controller->Factory->Paginator(sizeof($result), $ask, 'pane');
        $data['header']  = "<a href='/ui/'>Home</a> &#187; ";
        $data['header'] .= sprintf("<a href='%s'>%s</a> &#187; %s", $back, $this->groupName, $value); 
        $data['header'] .= "<div style='float:right'>{$bfave}{$bhilo}</div>";
        for($x=$low;$x<$hi&&$x<sizeof($result);$x++)
        {
            $name    = $result[$x]->id; 
            $value   = $result[$x]->subject; 
            $b64     = base64_encode ($name);
            $uri     = $this->Controller->URI (array('item'    => $name,
                                                     'pane'    => NULL));
            $src     = "/ui/image/group/{$this->groupName}/id/{$name}/thumb/ok";
            $data['main'] .= $this->Controller->Factory->Thumbnail ($src, $uri, $value);
        }
        return $this->Controller->Structure ($data); 
	}
    
    function ViewAsDetail($xml, $data)
    {
//		        article detail    
        
        $artid = $this->Controller->Settings['item'];
        $index = $this->Controller->Settings['index'];
        $queue = $this->Controller->Queue;   
        if (strlen($artid) > 0)
        { 
            $parent  = $xml->xpath("//list/article[@index='{$index}']");
            $result  = $xml->xpath("//list/article[@index='{$index}']/items/article"); 
            $items   = $xml->xpath("//article[contains(id, '{$artid}')]");  
//		            $images  = NULL;
            $item    = $items[0]; 
            $name    = $item->id; // NOTE: $name and $artid are the same value. Do we need this?
            $value   = $item->subject; 
            $type    = $parent[0]->type; 
          	$pref    = $parent[0]->ref;
            $arr     = explode ('-', $name);
            $key     = $arr[0];        
            $idx     = "data/tube/{$this->groupName}/{$key}.idx";
          	$image   = (!isset($type)) || $type=='' || $type=='picture';
//		            $ref     = explode('|', $pref);  
            
            $url     = $this->Controller->URI (array('ui'      => 'commandhandler',
                                                     'request' => 'index',
                                                     'item'    => NULL)) . '/item/';
            $fave    = $this->Controller->URI (array('ui'      => 'commandhandler',
                                                     'request' => 'mark'));
            $save    = $this->Controller->URI (array('ui'      => 'commandhandler',
                                                     'request' => 'get'));
            $back    = $this->Controller->URI (array('index'   => NULL,
                                                     'item'    => NULL));
            $b64     = base64_encode ($name);
            $picname = "data/temp/{$this->groupName}/{$b64}";
            $num     = sizeof($result); 
            $bfave   = $this->Controller->Factory->Button ($fave, 'Bookmark', 'i.p.cont.individual.gif'); 
            $bsave   = $this->Controller->Factory->Button ($save, "Save {$num} files", 'i.p.save.gif'); 
            $js      = 'location.href=this.className+this.options[this.selectedIndex].value';
            uasort($result, 'cmpx');
         
//		    media file, rar output or queued article   
            if (!$image && !$queue->Recall($name))
            {
                if (file_exists($idx))
                { // index files indicate M4V, RAR, Image List, or download in progress
                    $nfo     = simplexml_load_file($idx);
                    $picname = $nfo->name; // $nfo->name is an M4V file, M4V preview or Image List preview  
                    if ($type=='rar') 
                    {
                         $result  = $nfo->xpath ("//files/name");
                         if ($result && sizeof($result) > 0)
                         { // a list of files indicates an Image List
                             $js      = 'view(this.className+this.options[this.selectedIndex].value);';
                             $url     = "/data/perm/{$this->groupName}/{$key}/";
                             $picname = $nfo->picture;
                         }
                    }
                }
                else
                { // LEGACY: THERE SHOULD BE NO MORE .NAME FILES 
                    // $picname = trim($this->Controller->Read ("data/tube/{$this->groupName}/{$key}.name"));
					// not image, not in queue, no index file...
					echo "Article {$artid} - {$value} could not be found. The download or conversion of the file probably failed.";
                    echo $this->Controller->Factory->Button ($back, 'Back', 'i.p.cont.individual.gif'); 
					return;  
                }
                $bfave = "";
                $bsave = "";
            } 
        
//                  Render page header
            $data['header']  = "<a href='/ui/'>Home</a> &#187; ";
            $data['header'] .= sprintf("<a href='%s'>%s</a> &#187; %s", $back, $this->groupName, $value); 
            $data['header'] .= "<div style='float:right'>$bfave.$bsave </div>";   
            
//                  Page body
            $data['main'] = '<center>';  
            if ($queue->Recall($name))
            {
                $who = $queue->Param['Type'];
                $pic = $queue->Param['Picture'];
                $cap = $who == TYPE_RAR ? base64_decode($queue->Param['Subject']) : $queue->Param['Name'];
                $exc = $queue->GetStatus();
                $data['main'] .= "{$cap} is {$exc}...<br/><img src='/{$pic}'/>";
            }
            else if (file_exists($picname))
            {   
                if ($image || $type=='rar')
                { 
                    $player  = "";
                    switch ($this->Controller->GetType ($picname))
                    {
                        case TYPE_IMAGE: 
                            $player = "<a href='javascript:void(0)' onclick='donext(1);'>" . 
                                      "<img id='box' border='0' height='540' src='/{$picname}' />" . 
                                      "</a><br/>$picname";
                            break;  
                        case TYPE_MOVIE: // unrar'd video
                            $player = $this->Controller->Factory->VideoPlayer($picname);
                            break;  
                    } 
                    $data['main'] .= $player;  
                }
                else
                { // decoded video   
                    $data['main'] .= $this->Controller->Factory->VideoPlayer($picname);  
                }
            }
            $data['main'] .= '</center>';


//          Page control bar
            $data['controlbar'] = "<select class='{$url}' id='drp' onchange='{$js}'>"; 
            foreach ($result as $article)
            {
                $node  = $article->getName();
                $id    = explode('-', "{$article->id}");
                $name  = $node == 'name' ? "{$article}" : $id[0];
                $value = $node == 'name' ? "{$article}" : $article->subject;  
                $data['controlbar'] .= sprintf("<option value='%s' %s>%s</option>", $name, strpos($name,$artid)!==false?'selected':'', $value); 
            }
            $data['controlbar'] .= "</select>";
            $data['controlbar'] .= "<input type='button' value='Prev' onclick='donext(-1)' />";
            $data['controlbar'] .= "<input type='button' value='Next' onclick='donext(1)' /><br/>$pref";  
			
			
            echo $this->Controller->Structure ($data);
  		    return;
        }
//              End article detail    	  
	}
    
    function Display($write = false)
    {  
        if (!$write)
        { 
            $pageindex = $this->Controller->Settings['page'];
            $paneindex = $this->Controller->Settings['pane'];
            $find      = $this->Controller->Settings['find'];
            $seek      = $this->Controller->Settings['seek'];
            $index     = $this->Controller->Settings['index'];
            $pageitem  = $this->Controller->Settings['item'];
            $filename  = isset($seek) ? "data/find/{$this->groupName}/{$seek}.xml" : "data/{$this->groupName}.xml"; 
            $data      = array(); 
            $queue     = $this->Controller->Queue;
            if (file_exists($filename)) 
            {
		        $xml = simplexml_load_file($filename);
		        $data['toolbar'] = $this->Controller->Factory->TabBar('Server');  
                $xdb  = $xml->xpath("//list/article[string-length(ref) > 0]/ref");
                $xref = array(); 
                foreach ($xdb as $x)
                { // related groups
                    $tmp = explode ('|', "{$x}");
                    foreach ($tmp as $grp)
                    {
                        if (array_search($grp, $xref)===false && $grp != 'Xref' && $grp != $this->groupName)
                        {
                            $xref[] = $grp;
                        }
                    }
                }
                
//		        article detail       
		        if (strlen($pageitem) > 0)
		        {
		        	$this->ViewAsDetail($xml, $data);
					return; 
                }
//              End article detail
		        
//              article browsing  
                if (strlen($index) > 0)
                {
                	if ($this->Controller->Settings['view'] == 'hilo')
					{
						echo $this->ViewasHiLo($xml, $data);
						return;
					}
                    echo $this->ViewasBrowse ($xml, $data);  
					return;  
                }
                
				
				
				// begin article list
                
		        $total  = $xml->xpath("//article"); 
		        $result = $xml->xpath("//list/article"); 
		        $extra  = "";
		        
		        if (strlen($find) > 0)
		        {
		            $result = $xml->xpath("//list/article[contains(subject, '{$find}')]");  
		        }
		        else
		        {
		            $result = $this->Controller->SortArticles($result);
		        }
                
    
		        $view = new News_UI_View($this->Controller);
				
		        
		        
		        $header = $xml->xpath("//list");
//		        $blank  = "http://www.101stratford.com/webservices/images/clear.gif";
		        $hi     = $pageindex * UI_PAGE_SIZE;
		        $low    = $hi - UI_PAGE_SIZE;
		        $min    = $header[0]->min;
		        $max    = $header[0]->max;
		        $least  = $total[0]->id;
//		        $more   = $total[sizeof($total)-1]->id;
		        $more   = '';
		        $x      = sizeof($total)-1; $e = 0; 
		        while (strlen($more)==0 && ++$e < 100)
		        {
	                $more   = $total[$x--]->id;
	                $tmp    = explode ('-', $more);
	                $more   = $tmp[0];
		        } 
                $fave   = $this->Controller->URI (array('subscribe' => 'ok'));
                
                $renew  = $this->Controller->URI (array('ui'      => 'commandhandler',
                                                        'request' => 'renew'));
                
                $next   = $this->Controller->URI (array('ui'      => 'groupdialog',
                                                        'request' => 'renew',
                                                        'more'    => $more));  
		        if (strpos($least, '-')!==false) $least = substr($least, 0, strpos($least,'-'));
		        if (strpos($more, '-')!==false) $more = substr($more, 0, strpos($more,'-'));
		         
				if (sizeof($xref) > 0)
				{
			        $drp = "<select onchange='location.href=this.className+this.options[this.selectedIndex].value' class='/ui/commandhandler/request/group/group/'>";
			        $drp .= "<option>Related groups</option>";
			        foreach ($xref as $i)
			        {
			           $g = $this->Controller->GroupRename($i);
			           $drp .= "<option value='{$i}'>{$g}</option>";
			        }
			        $drp .= '</select>';
				}
				 
				$dir = "data/find/{$this->groupName}"; 
				if (is_dir($dir))
				{
					$maps = scandir ($dir);
			        $drm = "<select onchange='location.href=this.className+this.options[this.selectedIndex].value' class='/ui/commandhandler/group/{$this->groupName}/request/page/page/1/seek/'>";
			        $drm .= "<option>Saved searches</option>";
					foreach ($maps as $m)
					{
						$tmp = explode('.', $m); $g=$tmp[0]; $s=sel($g==$seek); #echo $s;
						if (strlen($g)>0) $drm .= "<option {$s} value='{$g}'>{$g}</option>";
					}
			        $drm .= '</select>';
				}
				
		        $view->Toolbar       = $this->Controller->Factory->TabBar('Server') . $drp . $drm . $this->Controller->Factory->ArticleSearchForm();
		        $view->Controlbar    = $this->Controller->Factory->Paginator(sizeof($result)); 
				$view->BreadCrumbs[] = "<a href='/ui/'>Home</a>";
				$view->BreadCrumbs[] = isset($seek) ? "<a href='/ui/articlelist/group/{$this->groupName}/page/1'>{$this->groupName}</a>" : "<b>{$this->groupName}</b>";
				$view->BreadCrumbs[] = isset($seek) ? "Search for $seek" : ($this->Controller->Factory->BatchList() . " of {$max} articles ");
				
				
				$view->Buttons[]     = array('uri'=>$renew, 'text'=>'Refresh Group', 'icon'=>'address-refresh.gif');
				$view->Buttons[]     = array('uri'=>$next,  'text'=>'Next ' . DOWNLOAD_PACKET_VOLUME, 'icon'=>'address-go.gif');
				$view->Buttons[]     = array('uri'=>$fave,  'text'=>$this->Subscribed()?'Unsubscribe':'Subscribe', 'icon'=>'icon-block-favourite.png'); 
				
                
		        for($x=$low;$x<$hi&&$x<sizeof($result);$x++)
		        {
		            $name    = $result[$x]->id;
		            $arr     = explode('-', $name);
		            $parts   = sizeof ($arr);
		            $value   = $result[$x]->subject;
		            // $ref     = $result[$x]->ref;
		            $type    = $result[$x]->type; 
		            $who     = $result[$x]->name; 
		            $when    = $result[$x]->date; 
		          	$image   = (!isset($type)) || $type=='' || $type=='picture';
		            $att     = $result[$x]->attributes();
		            $index   = $att['index'];
		            $kids    = $result[$x]->xpath("items/article");
		            $size    = sizeof ($kids); 
                    $b64     = base64_encode ($name);
                    $picname = "data/temp/{$this->groupName}/{$b64}";
                    
		            $uri     = array ('ui'      => 'commandhandler', 
		                              'request' => 'index', 
		                              'index'   => $index, 
		                              'item'    => $arr[0]
		                             );
		            $browse  = array ('ui'      => 'commandhandler', 
		                              'request' => 'browse', 
		                              'pane'    => 1, 
		                              'index'   => $index 
		                             );
		            $browse  = $this->Controller->Factory->Button($this->Controller->URI ($browse), 'Browse', 'i.p.search.gif'); 
		            $uri     = $this->Controller->URI ($uri);          
		                   
		            $error = "(Preview not available)";        
                    if (!$image)
                    {
                        $arr = explode ('-', $name);
                        $key = $arr[0]; 
                        $idx = "data/tube/{$this->groupName}/{$key}.idx";
                        $browse = 'Click to download';
                        if (file_exists($idx))
                        { 
                            $nfo     = simplexml_load_file($idx);
                            $picname = '/' . $nfo->picture;  
                            $browse  = "Video {$nfo->duration}";
                            $error   = NULL;
                        } 
                        else if ($queue->Recall($name))
                        {
                            $picname = '/' . $queue->Param['Picture']; 
                            $browse  = '<b>' . $queue->GetStatus() . '</b>';
                            $error   = NULL;
                        }
                        else
                        {
                            $picname = sprintf('/%s', $type=='rar' ? ICON_RAR : ICON_MOVIE);
                            $error   = NULL;
                        }
                    }
                    
                     
                    if (file_exists($picname) && !$queue->Recall($name))
                    {    
                        $error   = '';
                        $jpeg    = $picname . '.jpeg';
                        $picname = "/{$picname}";
                        
                        $picname = "/ui/image/group/{$this->groupName}/id/{$name}/thumb/ok";
                        if (file_exists($jpeg))
                        {
                            $picname = "/{$jpeg}";
                        }
                        else if (!$image)
                        {
                            $error = "Play {$picname}";
                        }
                    }  
					$caption = "{$browse} {$size} items, {$parts} parts" . 
                               "<br/>{$value}<br/>$who<br/>$when";
		 
					$view->Cells[] = array ('image'=>$picname, 'uri'=>$uri, 'caption'=>$caption, 'error'=>$error);
//                    echo $error;
                    $data['main'] .= $this->Controller->Factory->Thumbnail ($picname, $uri, $caption, $error);
                    
                     
		        }  

                echo $view->Display();
				return;

		        echo $this->Controller->Structure ($data);
            }   
            
            return;
        } 
    }      
}



function cmpx($a, $b) {
    return strcmp ($a->subject, $b->subject); 
}

